﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Cbs.Lucky.Events;
using Cbs.Lucky.Model;
using Cbs.Lucky.Services;
using Cbs.Lucky.Views;
using Newtonsoft.Json;
using NLog;
using Prism.Commands;
using Prism.Events;
using Prism.Mvvm;
using Prism.Regions;

namespace Cbs.Lucky.ViewModels
{
    public class CreateOrUpdateViewModel : BindableBase
    {
        private static Logger Logger = LogManager.GetCurrentClassLogger();
        public CreateOrUpdateViewModel(
            IRegionManager regionManager,
            IEventAggregator eventAggregator,
            IDataItemService dataItemService)
        {
            RegionManager = regionManager;
            _eventAggregator = eventAggregator;
            DataItemService = dataItemService;

            CloseCommand = new DelegateCommand(CloseCommandAction);
            SaveCommand = new DelegateCommand(async () => await SaveCommandAction());
        }

        private void CloseCommandAction()
        {
            _eventAggregator
                ?.GetEvent<CloseEvent>()
                ?.Publish(new CloseEventDetail
                {
                    TypeName = "CreateOrUpdate"
                });
        }

        private async Task SaveCommandAction()
        {
            try
            {
                Logger.Debug("CALL SaveCommandAction");
                Logger.Debug($"SaveCommandAction ${JsonConvert.SerializeObject(DataItemForm)}");
                var title = DataItemForm.Title;
                await DataItemService?.Save(new DataItem
                {
                    Id = title.ToInt32(),
                    Data = DataItemForm.Data,
                    CreateTime = DateTime.Now,
                    CurrentDaySeqNum = title.Substring(title.Length - 2).ToInt32()
                });
                CloseCommandAction();
                DataItemForm.Title = string.Empty;
                DataItemForm.FormData = string.Empty;
            }
            catch (Exception ex)
            {
                Logger.Error($"SaveCommandAction Message:{ex.Message},StackTrace:{ex.StackTrace}");
            }
        }

        public IRegionManager RegionManager { get; }

        private IEventAggregator _eventAggregator;

        public IDataItemService DataItemService { get; }

        private DataItemForm _dataItemForm = new DataItemForm();

        public DataItemForm DataItemForm
        {
            get { return _dataItemForm; }
            set { SetProperty(ref _dataItemForm, value); }
        }

        public DelegateCommand CloseCommand { get; }
        public DelegateCommand SaveCommand { get; }
    }

    public class DataItemForm : BindableBase, IDataErrorInfo
    {
        /// <summary>
        /// Data分割字符
        /// </summary>
        private string[] _dataSplitor = new[] { ","/*英文逗号*/, " "/*空格*/, "，"/*中文逗号*/, ";"/*英文分号*/, "；"/*中文分号*/ };
        public Dictionary<string, string> Errors { get; set; } = new Dictionary<string, string>();
        public string this[string colName]
        {
            get
            {
                var result = string.Empty;
                switch (colName)
                {
                    case nameof(Title):
                        if (Title.IsNullOrWhiteSpace())
                        {
                            result = "期号不能为空";
                        }
                        else if (Title?.Length != 10 || !Title.IsValidInt32())
                        {
                            result = "期号只能是10位数字";
                        }
                        break;
                    case nameof(FormData):
                        if (FormData.IsNullOrWhiteSpace())
                        {
                            result = "数据不能为空";
                        }
                        else
                        {
                            var datas = FormData.Split(_dataSplitor, StringSplitOptions.RemoveEmptyEntries);
                            if (datas.Length != 5)
                            {
                                result = "请输入5组数字";
                            }
                            else if (datas.Any(a => !a.IsValidInt32()))
                            {
                                result = "请输入5组数字";
                            }
                            else if (datas.Distinct().Count() != 5)
                            {
                                result = "请输入5组不重复数字";
                            }
                            else if (datas.Any(a => a.ToInt32() <= 0 || a.ToInt32() > 11))
                            {
                                result = "请输入5组1-11区间的不重复数字";
                            }
                        }
                        break;
                    default:
                        break;
                }
                if (result.IsNotNullOrWhiteSpace())
                {
                    Errors?.AddIfNotContainsKey(colName, result);
                }
                else
                {
                    Errors?.Remove(colName);
                }
                RaisePropertyChanged(nameof(CanSave));
                return result;
            }
        }
        private string _title;
        private string _data;
        private string _formData;

        public bool CanSave
        {
            get { return !HasErrors; }
            //set { SetProperty(ref _canSave, value); }
        }

        /// <summary>
        /// 表单数据
        /// </summary>
        public string FormData
        {
            get { return _formData; }
            set
            {
                SetProperty(ref _formData, value);
                SetProperty(ref _data, value, nameof(Data));
            }
        }

        /// <summary>
        /// 实际数据
        /// </summary>
        public string Data
        {
            get
            {
                if (_data == null)
                {
                    return string.Empty;
                }
                var datas = _data.Split(_dataSplitor, StringSplitOptions.RemoveEmptyEntries);
                var newData = string.Join(",", datas
                    .Where(w => w.IsValidInt32())
                    .Select(s => s.PadLeft(2, '0')));
                return newData;
            }
            set
            {
                SetProperty(ref _data, value);
            }
        }

        public string Title
        {
            get { return _title; }
            set { SetProperty(ref _title, value); }
        }

        public string Error => string.Empty;

        public bool HasErrors => Errors.Any();
    }
}
